// 文件名称：sync.js
// 完整保存路径：miniprogram/utils/sync.js
// 功能说明：数据同步和缓存服务
// 使用说明：处理离线数据缓存、数据同步和冲突解决

const { getToken } = require('./auth');

/**
 * 数据同步和缓存服务
 */
class DataSyncService {
  constructor() {
    this.syncQueue = []; // 同步队列
    this.isSyncing = false; // 是否正在同步
    this.lastSyncTime = null; // 最后同步时间
  }

  /**
   * 初始化同步服务
   */
  async init() {
    try {
      // 从本地存储获取最后同步时间
      const lastSync = wx.getStorageSync('lastSyncTime');
      if (lastSync) {
        this.lastSyncTime = new Date(lastSync);
      }

      // 检查是否有待同步的数据
      await this.checkPendingSync();
      
      // 启动定期同步
      this.startPeriodicSync();
      
      console.log('数据同步服务初始化完成');
    } catch (error) {
      console.error('数据同步服务初始化失败:', error);
    }
  }

  /**
   * 缓存数据到本地存储
   * @param {string} key 缓存键
   * @param {any} data 数据
   * @param {number} ttl 过期时间（秒）
   */
  cacheData(key, data, ttl = 3600) {
    try {
      const cacheItem = {
        data: data,
        timestamp: Date.now(),
        ttl: ttl * 1000
      };
      wx.setStorageSync(key, cacheItem);
      console.log(`数据已缓存: ${key}`);
    } catch (error) {
      console.error('缓存数据失败:', error);
    }
  }

  /**
   * 从本地存储获取缓存数据
   * @param {string} key 缓存键
   * @returns {any|null} 缓存数据或null
   */
  getCachedData(key) {
    try {
      const cacheItem = wx.getStorageSync(key);
      if (!cacheItem) {
        return null;
      }

      // 检查是否过期
      const now = Date.now();
      if (now - cacheItem.timestamp > cacheItem.ttl) {
        wx.removeStorageSync(key);
        return null;
      }

      return cacheItem.data;
    } catch (error) {
      console.error('获取缓存数据失败:', error);
      return null;
    }
  }

  /**
   * 清除缓存数据
   * @param {string} key 缓存键
   */
  clearCache(key) {
    try {
      wx.removeStorageSync(key);
      console.log(`缓存已清除: ${key}`);
    } catch (error) {
      console.error('清除缓存失败:', error);
    }
  }

  /**
   * 清除所有缓存
   */
  clearAllCache() {
    try {
      const keys = wx.getStorageInfoSync().keys;
      keys.forEach(key => {
        if (key.startsWith('cache_')) {
          wx.removeStorageSync(key);
        }
      });
      console.log('所有缓存已清除');
    } catch (error) {
      console.error('清除所有缓存失败:', error);
    }
  }

  /**
   * 添加数据到同步队列
   * @param {string} type 操作类型
   * @param {any} data 数据
   * @param {string} endpoint API端点
   */
  addToSyncQueue(type, data, endpoint) {
    const syncItem = {
      id: Date.now() + Math.random(),
      type: type,
      data: data,
      endpoint: endpoint,
      timestamp: Date.now(),
      retryCount: 0
    };

    this.syncQueue.push(syncItem);
    this.saveSyncQueue();
    console.log(`数据已添加到同步队列: ${type}`);
  }

  /**
   * 保存同步队列到本地存储
   */
  saveSyncQueue() {
    try {
      wx.setStorageSync('syncQueue', this.syncQueue);
    } catch (error) {
      console.error('保存同步队列失败:', error);
    }
  }

  /**
   * 从本地存储加载同步队列
   */
  loadSyncQueue() {
    try {
      const queue = wx.getStorageSync('syncQueue');
      if (queue && Array.isArray(queue)) {
        this.syncQueue = queue;
      }
    } catch (error) {
      console.error('加载同步队列失败:', error);
      this.syncQueue = [];
    }
  }

  /**
   * 检查待同步的数据
   */
  async checkPendingSync() {
    this.loadSyncQueue();
    
    if (this.syncQueue.length > 0) {
      console.log(`发现 ${this.syncQueue.length} 条待同步数据`);
      await this.processSyncQueue();
    }
  }

  /**
   * 处理同步队列
   */
  async processSyncQueue() {
    if (this.isSyncing || this.syncQueue.length === 0) {
      return;
    }

    this.isSyncing = true;
    console.log('开始处理同步队列...');

    try {
      const token = getToken();
      if (!token) {
        console.log('未登录，跳过同步');
        return;
      }

      const itemsToProcess = [...this.syncQueue];
      const successItems = [];
      const failedItems = [];

      for (const item of itemsToProcess) {
        try {
          await this.syncItem(item);
          successItems.push(item);
        } catch (error) {
          console.error(`同步失败: ${item.type}`, error);
          item.retryCount++;
          
          if (item.retryCount < 3) {
            failedItems.push(item);
          } else {
            console.log(`同步重试次数已达上限: ${item.type}`);
          }
        }
      }

      // 更新同步队列
      this.syncQueue = failedItems;
      this.saveSyncQueue();

      // 更新最后同步时间
      this.lastSyncTime = new Date();
      wx.setStorageSync('lastSyncTime', this.lastSyncTime.toISOString());

      console.log(`同步完成: 成功 ${successItems.length} 条，失败 ${failedItems.length} 条`);
    } catch (error) {
      console.error('处理同步队列失败:', error);
    } finally {
      this.isSyncing = false;
    }
  }

  /**
   * 同步单个数据项
   * @param {Object} item 同步项
   */
  async syncItem(item) {
    const token = getToken();
    if (!token) {
      throw new Error('未登录');
    }

    return new Promise((resolve, reject) => {
      wx.request({
        url: `${getApp().globalData.apiBaseUrl}${item.endpoint}`,
        method: item.type === 'create' ? 'POST' : item.type === 'update' ? 'PUT' : 'DELETE',
        header: {
          'Authorization': `Bearer ${token}`,
          'Content-Type': 'application/json'
        },
        data: item.data,
        success: (res) => {
          if (res.data.success) {
            resolve(res.data);
          } else {
            reject(new Error(res.data.message || '同步失败'));
          }
        },
        fail: (error) => {
          reject(new Error('网络请求失败: ' + error.errMsg));
        }
      });
    });
  }

  /**
   * 启动定期同步
   */
  startPeriodicSync() {
    // 每5分钟检查一次同步
    setInterval(() => {
      this.processSyncQueue();
    }, 5 * 60 * 1000);
  }

  /**
   * 强制同步
   */
  async forceSync() {
    console.log('强制同步开始...');
    await this.processSyncQueue();
  }

  /**
   * 获取同步状态
   */
  getSyncStatus() {
    return {
      isSyncing: this.isSyncing,
      queueLength: this.syncQueue.length,
      lastSyncTime: this.lastSyncTime
    };
  }

  /**
   * 网络状态变化处理
   */
  onNetworkChange(isConnected) {
    if (isConnected && this.syncQueue.length > 0) {
      console.log('网络恢复，开始同步...');
      this.processSyncQueue();
    }
  }
}

// 创建全局实例
const dataSyncService = new DataSyncService();

// 导出实例和工具函数
module.exports = {
  dataSyncService,
  
  // 缓存相关
  cacheData: (key, data, ttl) => dataSyncService.cacheData(key, data, ttl),
  getCachedData: (key) => dataSyncService.getCachedData(key),
  clearCache: (key) => dataSyncService.clearCache(key),
  clearAllCache: () => dataSyncService.clearAllCache(),
  
  // 同步相关
  addToSyncQueue: (type, data, endpoint) => dataSyncService.addToSyncQueue(type, data, endpoint),
  forceSync: () => dataSyncService.forceSync(),
  getSyncStatus: () => dataSyncService.getSyncStatus(),
  
  // 初始化
  initSyncService: () => dataSyncService.init()
}; 